home *** CD-ROM | disk | FTP | other *** search
/ Amiga Plus 1995 #1 / Amiga Plus 1995 #1.iso / animationen / retina_fli_ii / retinaflick.c < prev    next >
C/C++ Source or Header  |  1994-12-13  |  6KB  |  258 lines

  1. /* retinaflick.c
  2.    Robert Poole
  3. */
  4.  
  5. #include <stdlib.h>
  6. #include <stdio.h>
  7.  
  8. #include <exec/libraries.h>
  9.  
  10. #include <clib/exec_protos.h>
  11. #include <clib/intuition_protos.h>
  12. #include <devices/timer.h>
  13. #include <clib/alib_protos.h>
  14. #include <time.h>
  15.  
  16. #include <libraries/retina.h>
  17. #include <clib/retina_protos.h>
  18. #include <pragmas/retina_pragmas.h>
  19.  
  20. #include "xflick.h"
  21. #include "time_routines.h"
  22.  
  23. #define USE_WRITERECT 1
  24.  
  25. extern struct IntuitionBase *IntuitionBase;
  26. struct _xy_RetinaBase *RetinaBase;
  27. struct DefaultScreenInfo screen_info;
  28.  
  29. int __oslibversion = 37;
  30.  
  31. struct RetinaScreen *rScreen;
  32. verbose = 0;
  33. int memwidth, scrheight;
  34. /* for timing */
  35. static int usecs, secs;
  36. static int fdelay = -1;     /* frame delay */
  37.  
  38. /* prototypes */
  39. static void convert_fdelay(void);
  40. static void func_disp(int, int, unsigned char *, int, int, int, int, int, int);
  41.  
  42.  
  43. /* where the real functions are */
  44. static void convert_fdelay(void)
  45. {
  46.   usecs = (fdelay % 70) * 14285;
  47.   secs = fdelay / 70;
  48. }
  49.  
  50. int main(int argc, char *argv[])
  51. {
  52.   register int i;
  53.   int fd;
  54.   struct fli_header flihead;
  55.   unsigned char *data = NULL;
  56.   int repeatcount = 2;
  57.   unsigned char notfirst = 0;
  58.  
  59.   if (!setup_timer()) {
  60.     fprintf(stderr, "Can't allocate timer resources.\n");
  61.     exit(-1);
  62.   }
  63.  
  64.   if (argc > 1) {
  65.     for (i = 1; i < argc; i++) {
  66.       if (argv[i][0] != '-') {
  67.     fd = open(argv[i], 0);
  68.     if (fd < 0) {
  69.       fprintf(stderr, "Can't open file %s.\n", argv[i]);
  70.       exit(-1);
  71.     }
  72.     read_flihead(fd, &flihead);
  73.       }
  74.       else {
  75.     switch(argv[i][1]) {
  76.     case 'd':
  77.       fdelay = atoi(argv[i] + 2);
  78.       printf("Frame delay of %d/70 sec.\n", fdelay);
  79.       break;
  80.  
  81.     case 'r':
  82.       repeatcount = atoi(argv[i] + 2);
  83.       printf("Will loop animation %d times.\n", repeatcount);
  84.       break;
  85.  
  86.     case '?':
  87.     case 'h':
  88.       printf("Usage:\n");
  89.       printf("%s [flags] filename\n", argv[0]);
  90.       printf("Flags:\n");
  91.       printf("-d<number>\tFrame delay in 1/70th of a sec.\n");
  92.       printf("-r<number>\tRepeat count.\n");
  93.       printf("-?\tThis information display.\n");
  94.       printf("-h\n");
  95.       exit(0);
  96.       break;
  97.  
  98.     default:
  99.       fprintf(stderr, "Warning: illegal option %s\n", argv[i]);
  100.       break;
  101.     }
  102.       }
  103.     }
  104.   }
  105.   else {
  106.     fprintf(stderr, "Must start from shell, and must supply filename.\n");
  107.     exit(-1);
  108.   }
  109.  
  110.   if ((flihead.fhd_magic & 0x0000ffff) != FLI_MAGIC &&
  111.       (flihead.fhd_magic & 0x0000ffff) != FLC_MAGIC) {
  112.     fprintf(stderr, "%s is not a FLI/FLC file.\n", argv[1]);
  113.     exit(0);
  114.   }
  115.  
  116.   if (fdelay < 0) {
  117.     fdelay = flihead.fhd_speed;
  118.   }
  119.   convert_fdelay();
  120.  
  121.   data = (unsigned char *) malloc(flihead.fhd_width * flihead.fhd_height);
  122.   if (data == NULL) {
  123.     fprintf(stderr, "Failed to allocate %d bytes.\n",
  124.         flihead.fhd_width * flihead.fhd_height);
  125.     exit(-1);
  126.   }
  127.  
  128.   if ((RetinaBase = (struct _xy_RetinaBase *)
  129.        OpenLibrary("retina.library", RETINA_LIB_VERSION)) != NULL) {
  130.     if ((rScreen = Retina_OpenScreen(memwidth = flihead.fhd_width,
  131.                      scrheight = flihead.fhd_height,
  132.                      MID_DEFAULT_08,
  133.                      RSFF_DOUBLEBUFFER | RSFF_DBUFPALETTE,
  134.                      NULL))
  135.     != NULL) {
  136.       /* screen has opened successfully, we can do our thing now */
  137.  
  138.       while (repeatcount--) {
  139.     interpret_fli(fd, &flihead, data, notfirst, func_disp);
  140.     notfirst = 1;
  141.       }
  142.  
  143.       /* clean up now */
  144.       close(fd);
  145.       free(data);
  146.       dispose_timer_resources();
  147.       Retina_CloseScreen(rScreen);
  148.       CloseLibrary((struct Library *) RetinaBase);
  149.       exit(0);
  150.     }
  151.     else {
  152.       fprintf(stderr, "Couldn't open double buffered Retina screen.\n");
  153.       if (data)
  154.     free(data);
  155.       dispose_timer_resources();
  156.       exit(-1);
  157.     }
  158.   }
  159.   else {
  160.     fprintf(stderr, "Couldn't open retina.library version %ld.\n",
  161.         RETINA_LIB_VERSION);
  162.     if (data)
  163.       free(data);
  164.     dispose_timer_resources();
  165.     exit(-1);
  166.   }
  167. }
  168.  
  169. static void func_disp(int ftype, int frame, unsigned char *buf,
  170.               int srcx, int srcy, int destx, int desty,
  171.               int swidth, int sheight)
  172. {
  173.   static int colchange = 0;  /* colormap has changed */
  174. #ifndef USE_WRITERECT
  175.   register int i, j;
  176. #endif
  177.  
  178.   switch (ftype) {
  179.   case FLI_COPY:
  180.   case FLI_LC:
  181.   case FLI_DELTA:
  182.   case FLI_BRUN:
  183.  
  184. #ifdef USE_WRITERECT
  185.     Retina_WriteRect(buf, srcx, srcy, memwidth,
  186.              RECTMODE_256 | RECTMODEF_BYTEMEMWIDTH,
  187.              rScreen,
  188.              destx, desty, swidth, sheight, NULL);
  189. #else
  190.     for (j = 0; j < sheight; j++) {
  191.       for (i = 0; i < swidth; i++) {
  192.     Retina_SetAPen(rScreen, *(buf + srcx + i + (srcy + j)*memwidth));
  193.     Retina_WritePixel(rScreen, i + destx, j + desty);
  194.       }
  195.     }
  196. #endif
  197.  
  198.     /* we can now swap the double-buffered bitmaps */
  199.     Retina_SwapBitMap(rScreen);
  200.     Retina_CopyRect(rScreen, destx, desty, swidth, sheight, rScreen,
  201.             destx, desty, /* damage region */
  202.             CRF_SRCDBUF);
  203.     break;
  204.  
  205.   case FLI_BLACK:
  206. #ifdef debug
  207.     printf("I am setting a region black.\n");
  208. #endif
  209.     Retina_SetAPen(rScreen, 0x00000000L); /* we want BLACK! */
  210.     Retina_RectFill(rScreen, destx, desty,
  211.             destx + swidth, desty + sheight);
  212.     break;
  213.  
  214.   case FLI_COLOR:
  215.     while (srcy--) {
  216.       UBYTE color, red, grn, blu;
  217.  
  218.       Retina_SetPalette(rScreen, color = srcx++,
  219.             red = ((*(buf++) & 0x3f) << 2),
  220.             grn = ((*(buf++) & 0x3f) << 2),
  221.             blu = ((*(buf++) & 0x3f) << 2));
  222. #ifdef DEBUG
  223.       printf("Setting color %d to R%2x G%2x B%2x\n",
  224.          color, red, grn, blu);
  225. #endif
  226.     }
  227.     colchange = 1;
  228.     break;
  229.  
  230.   case FLI_256_COLOR:
  231.     while (srcy--) {
  232.       UBYTE color, red, grn, blu;
  233.  
  234.       Retina_SetPalette(rScreen, color = srcx++,
  235.             red = (*(buf++) & 0xff),
  236.             grn = (*(buf++) & 0x3f),
  237.             blu = (*(buf++) & 0x3f));
  238. #ifdef DEBUG
  239.       printf("Setting color %d to R%2x G%2x B%2x\n",
  240.          color, red, grn, blu);
  241. #endif
  242.     }
  243.     colchange = 1;
  244.     break;
  245.  
  246.   case FLI_SYNC:
  247.     if (colchange) {
  248.       colchange = 0;
  249.     }
  250.     /* is there a frame delay? */
  251.     if (usecs || secs) {
  252.       /* wait for frame delay */
  253.       synchronous_wait(secs, usecs);
  254.     }
  255.     break;
  256.   }
  257. }
  258.